const jwtUtils = require('../utils/jwtUtils');
const User = require('../models/user');

/**
 * 认证中间件
 * 验证用户的访问令牌并将用户信息附加到上下文
 */
const authMiddleware = async (ctx, next) => {
  try {
    // 从请求头获取令牌
    const authHeader = ctx.headers.authorization;
    
    if (!authHeader || !authHeader.startsWith('Bearer ')) {
      ctx.status = 401;
      ctx.body = {
        success: false,
        message: '未提供有效的认证令牌'
      };
      return;
    }
    
    const token = authHeader.split(' ')[1];
    
    // 验证令牌
    const decoded = jwtUtils.verifyAccessToken(token);
    
    if (!decoded) {
      ctx.status = 401;
      ctx.body = {
        success: false,
        message: '无效或过期的令牌'
      };
      return;
    }
    
    // 查找用户
    const user = await User.findById(decoded.userId);
    
    if (!user || user.status !== 'active') {
      ctx.status = 401;
      ctx.body = {
        success: false,
        message: '用户不存在或已被禁用'
      };
      return;
    }
    
    // 将用户信息附加到上下文
    ctx.state.user = user;
    ctx.state.userId = user._id;
    ctx.state.role = user.role;
    
    await next();
  } catch (error) {
    console.error('认证中间件错误:', error);
    ctx.status = 401;
    ctx.body = {
      success: false,
      message: '认证失败'
    };
  }
};

/**
 * 角色验证中间件
 * @param {Array<string>} allowedRoles - 允许访问的角色列表
 */
const roleMiddleware = (allowedRoles) => {
  return async (ctx, next) => {
    try {
      // 确保用户已经通过了认证中间件
      if (!ctx.state.user || !ctx.state.role) {
        ctx.status = 401;
        ctx.body = {
          success: false,
          message: '未认证'
        };
        return;
      }
      
      // 检查用户角色是否在允许的角色列表中
      if (!allowedRoles.includes(ctx.state.role)) {
        ctx.status = 403;
        ctx.body = {
          success: false,
          message: '权限不足'
        };
        return;
      }
      
      await next();
    } catch (error) {
      console.error('角色验证中间件错误:', error);
      ctx.status = 500;
      ctx.body = {
        success: false,
        message: '服务器内部错误'
      };
    }
  };
};

module.exports = {
  authMiddleware,
  roleMiddleware
};